package item18;

import java.util.AbstractList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * 第18条：接口优于抽象类
 */
public class Test01 {

    public static void main(String[] args) {
        // 接口和抽象类
        // 最明显区别：抽象类允许包含某些方法的实现，但是接口则不允许
        // 重要的区别：为了实现由抽象类定义的类型，类必须成为抽象类的一个子类。
        //             任何一个类，只要它定义了所有必要的方法，并且遵守通用约定，它就被允许实现一个接口，而不管这个类是处于类层次的哪个位置。
        // java 只允许单继承，所以抽象类作为类型定义受到了极大的限制。

        // 现有的类可以很容易被更新，以实现新的接口。
        // 接口是定义mixin(混合类型)的理想选择。
        // 接口允许我们构造非层次结构的类型框架。
        /**
         * @see Singer 歌唱家
         * @see Songwriter 作曲家
         * @see SingerSongwriter 既是歌唱家也是作曲家
         */
        // 接口使得安全地增强类的功能成可为可能。
        // 通过对你导出的每个重要接口都提供一个抽象的骨架实现(skeletal implementation)类，把接口和抽象类的优点结合起来。
        /**
         * 命名一般为AbstractInterface
         * interface是指所实现的接口的名字。
         *
         * Collections Framework 为每个重要的集合都提供了一个骨架实现。
         * @see java.util.AbstractCollection
         * @see java.util.AbstractSet
         * @see java.util.AbstractList
         * @see java.util.AbstractMap
         *
         */

        /**
         * @see AbstractMapEntry
         */

        // 抽象类的演变比接口的演变要容易得多
        // 接口一旦被公开发行，并且已被广泛实现，再想改变这个接口几乎是不可能的。

    }

    // adapter 适配器
    // concrete implementation built atop skeletal implementation
    // 在骨架上构建具体的实现
    static List<Integer> intArrayAsList(final int[] a) {
        if (a == null)
            throw new NullPointerException();
        return new AbstractList<Integer>() {
            @Override
            public Integer get(int index) {
                return a[index];
            }

            @Override
            public int size() {
                return a.length;
            }

            @Override
            public Integer set(int index, Integer element) {
                return super.set(index, element);
            }
        };
    }

}
